/***********************************************************************************
 * 文件名： bmlite.c
 * 版本�?4
 * 说明�?
 * 		一个极度精简的电池管理组件，提供基本的电池事件通知�?
 *      在合适的地方调用 BMLite_Loop() 确保其在100ms左右执行一次。在程序启动时调用一�?
 *  BMLite_Init() 初始化本组件。通过 BMLite_SetRefreshStatus 可以暂时关闭或者启动状态刷新�?
 *  可以调用对应的函数接口主动获取一些状态，这些接口在头文件中有申明和说明。当有状态变化时�?
 *  本组件会通过调用 BMLite_Event 来进行通知，你必须在需要接收通知的地方定�?BMLite_Event 
 *  函数，它的使用类似一个中断函数，通过名称来识别，函数原型�?
 *  void BMLite_Event(bmlite_ev_t e)�?
 *      必须�?bmlite_config.h 文件中进行合适的配置，本组件才能工作在你期望的状态�?
 * 修改记录�?
 * 	2021/04/29: 初版�?刘言�?
 *  2021/05/07: 增加获取电池电量的功能。刘言�?
 *  2021/05/17: 增加当启用SWST且充电器接入时，仅在MOS开启时进行ADC采集的功能。刘言�?
***********************************************************************************/
#include "cpt-bmlite.h"
#include "polsys.h"

// 预处�?

#if (_BMLITE_MAX_ADV > 255)
typedef u16 bmlite_adv_t;
#else
typedef u8 bmlite_adv_t;
#endif

#if (_BMLITE_AD_MODE == 0)
#define _BMLITE_FLOAT_VOLTAGE_ADV (bmlite_adv_t)((u32)_BMLITE_VREF * _BMLITE_MAX_ADV / _BMLITE_FLOAT_VOLTAGE)
#define _BMLITE_OVER_VOLTAGE_ADV (bmlite_adv_t)((u32)_BMLITE_VREF * _BMLITE_MAX_ADV / _BMLITE_OVER_VOLTAGE)
#define _BMLITE_NO_BATTERY_VOLTAGE_ADV (bmlite_adv_t)((u32)_BMLITE_VREF * _BMLITE_MAX_ADV / _BMLITE_NO_BATTERY_VOLTAGE)
#define _BMLITE_HAS_BATTERY_VOLTAGE_ADV (bmlite_adv_t)((u32)_BMLITE_VREF * _BMLITE_MAX_ADV / _BMLITE_HAS_BATTERY_VOLTAGE)
#else
#define _BMLITE_FLOAT_VOLTAGE_ADV2 (bmlite_adv_t)((u32)((u32)_BMLITE_FLOAT_VOLTAGE2 * _BMLITE_LOW_RES / (_BMLITE_HIGH_RES + _BMLITE_LOW_RES)) * _BMLITE_MAX_ADV / _BMLITE_ADC_VREF)

#define _BMLITE_FLOAT_VOLTAGE_ADV (bmlite_adv_t)((u32)((u32)_BMLITE_FLOAT_VOLTAGE * _BMLITE_LOW_RES / (_BMLITE_HIGH_RES + _BMLITE_LOW_RES)) * _BMLITE_MAX_ADV / _BMLITE_ADC_VREF)
#define _BMLITE_OVER_VOLTAGE_ADV (bmlite_adv_t)((u32)((u32)_BMLITE_OVER_VOLTAGE * _BMLITE_LOW_RES / (_BMLITE_HIGH_RES + _BMLITE_LOW_RES)) * _BMLITE_MAX_ADV / _BMLITE_ADC_VREF)
#define _BMLITE_NO_BATTERY_VOLTAGE_ADV (bmlite_adv_t)((u32)((u32)_BMLITE_NO_BATTERY_VOLTAGE * _BMLITE_LOW_RES / (_BMLITE_HIGH_RES + _BMLITE_LOW_RES)) * _BMLITE_MAX_ADV / _BMLITE_ADC_VREF)
#define _BMLITE_HAS_BATTERY_VOLTAGE_ADV (bmlite_adv_t)((u32)((u32)_BMLITE_HAS_BATTERY_VOLTAGE * _BMLITE_LOW_RES / (_BMLITE_HIGH_RES + _BMLITE_LOW_RES)) * _BMLITE_MAX_ADV / _BMLITE_ADC_VREF)
#endif

#define _BMLITE_FLOAT_TIME_VAL (_BMLITE_FLOAT_TIME * 10)

// 属性定�?

bit _BMLite_mIsCharging = false;
bit _BMLite_mDCConnected = false;
bit _BMLite_mRunning;
bit _BMLite_mNoBattery;
static bit BMLite_mFull;
static u16 BMLite_mFloatTime;

#ifdef _BMLITE_USE_SWST
static u8 BMLite_mDcInTime;
#endif

#ifdef _BMLITE_USE_DC_OUT_DELAY
static u8 BMLite_mDcOutTime;
#endif

#ifdef _BMLITE_USE_BATT_LEVEL
u8 _BMLite_mLevel; // 电池电量百分�?
#define _BMLITE_L100_VOLTAGE _BMLITE_FLOAT_VOLTAGE
#define _BMLITE_L80_VOLTAGE (_BMLITE_FLOAT_VOLTAGE - 100)
#define _BMLITE_L60_VOLTAGE 3880
#define _BMLITE_L40_VOLTAGE 3730
#define _BMLITE_L20_VOLTAGE 3600
#define _BMLITE_L5_VOLTAGE _BMLITE_NO_BATTERY_VOLTAGE
#if (_BMLITE_AD_MODE == 0)
#define _BMLITE_L100_ADV (bmlite_adv_t)((u32)_BMLITE_VREF * _BMLITE_MAX_ADV / _BMLITE_L100_VOLTAGE)
#define _BMLITE_L80_ADV (bmlite_adv_t)((u32)_BMLITE_VREF * _BMLITE_MAX_ADV / _BMLITE_L80_VOLTAGE)
#define _BMLITE_L60_ADV (bmlite_adv_t)((u32)_BMLITE_VREF * _BMLITE_MAX_ADV / _BMLITE_L60_VOLTAGE)
#define _BMLITE_L40_ADV (bmlite_adv_t)((u32)_BMLITE_VREF * _BMLITE_MAX_ADV / _BMLITE_L40_VOLTAGE)
#define _BMLITE_L20_ADV (bmlite_adv_t)((u32)_BMLITE_VREF * _BMLITE_MAX_ADV / _BMLITE_L20_VOLTAGE)
#define _BMLITE_L5_ADV (bmlite_adv_t)((u32)_BMLITE_VREF * _BMLITE_MAX_ADV / _BMLITE_L5_VOLTAGE)
#else
#define _BMLITE_L100_ADV (bmlite_adv_t)((u32)((u32)_BMLITE_L100_VOLTAGE * _BMLITE_HIGH_RES / (_BMLITE_HIGH_RES + _BMLITE_LOW_RES)) * _BMLITE_MAX_ADV / _BMLITE_ADC_VREF)
#define _BMLITE_L80_ADV (bmlite_adv_t)((u32)((u32)_BMLITE_L80_VOLTAGE * _BMLITE_HIGH_RES / (_BMLITE_HIGH_RES + _BMLITE_LOW_RES)) * _BMLITE_MAX_ADV / _BMLITE_ADC_VREF)
#define _BMLITE_L60_ADV (bmlite_adv_t)((u32)((u32)_BMLITE_L60_VOLTAGE * _BMLITE_HIGH_RES / (_BMLITE_HIGH_RES + _BMLITE_LOW_RES)) * _BMLITE_MAX_ADV / _BMLITE_ADC_VREF)
#define _BMLITE_L40_ADV (bmlite_adv_t)((u32)((u32)_BMLITE_L40_VOLTAGE * _BMLITE_HIGH_RES / (_BMLITE_HIGH_RES + _BMLITE_LOW_RES)) * _BMLITE_MAX_ADV / _BMLITE_ADC_VREF)
#define _BMLITE_L20_ADV (bmlite_adv_t)((u32)((u32)_BMLITE_L20_VOLTAGE * _BMLITE_HIGH_RES / (_BMLITE_HIGH_RES + _BMLITE_LOW_RES)) * _BMLITE_MAX_ADV / _BMLITE_ADC_VREF)
#define _BMLITE_L5_ADV (bmlite_adv_t)((u32)((u32)_BMLITE_L5_VOLTAGE * _BMLITE_HIGH_RES / (_BMLITE_HIGH_RES + _BMLITE_LOW_RES)) * _BMLITE_MAX_ADV / _BMLITE_ADC_VREF)
#endif
#endif

// 声明引用事件通知函数（避免使用函数指针的妥协�?
// 在你的应用代码中定义这个函数用于接收事件
void BMLite_Event(bmlite_ev_t e);

// 文件内函数申�?

//static void RefreshStat();

// 对外提供的函�?

// void BMLite_Init()
// {
// }

void BMLite_Loop() //100ms执行一�?
{
    if (_BMLite_mRunning)
    {
        //更新充电状�?充电器是否接入，是否正在充电
        bmlite_adv_t adv;
#if (defined _BMLITE_ADC_ONLY_ON) && (defined _BMLITE_USE_SWST)
        if (_BMLite_mDCConnected)
        {
            if (BMLite_mDcInTime >= 1)
                adv = _BMLite_GetADValue();
        }
        else
            adv = _BMLite_GetADValue();
#else
        adv = _BMLite_GetADValue();
#endif
#ifdef _BMLITE_USE_BATT_LEVEL
            // 更新电池电量
#if (_BMLITE_AD_MODE == 0)
        if (adv <= _BMLITE_L100_ADV)
            _BMLite_mLevel = 100;
        else if (adv <= _BMLITE_L80_ADV)
            _BMLite_mLevel = 80;
        else if (adv <= _BMLITE_L60_ADV)
            _BMLite_mLevel = 60;
        else if (adv <= _BMLITE_L40_ADV)
            _BMLite_mLevel = 40;
        else if (adv <= _BMLITE_L20_ADV)
            _BMLite_mLevel = 20;
        else if (adv <= _BMLITE_L5_ADV)
            _BMLite_mLevel = 5;
        else
            _BMLite_mLevel = 0;
#else
        if (adv >= _BMLITE_L100_ADV)
            _BMLite_mLevel = 100;
        else if (adv >= _BMLITE_L80_ADV)
            _BMLite_mLevel = 80;
        else if (adv >= _BMLITE_L60_ADV)
            _BMLite_mLevel = 60;
        else if (adv >= _BMLITE_L40_ADV)
            _BMLite_mLevel = 40;
        else if (adv >= _BMLITE_L20_ADV)
            _BMLite_mLevel = 20;
        else if (adv >= _BMLITE_L5_ADV)
            _BMLite_mLevel = 5;
        else
            _BMLite_mLevel = 0;
#endif
#endif
        if (_BMLite_GetDCStatus()) //充电器接�?
        {
#ifdef _BMLITE_USE_DC_OUT_DELAY
            BMLite_mDcOutTime = 0;
#endif
#ifdef _BMLITE_USE_SWST
            BMLite_mDcInTime++;
            if (BMLite_mDcInTime == 10)
            {
                BMLite_mDcInTime = 0;
                _BMLite_StopChrg();
            }
            else if (BMLite_mDcInTime == 1)
            {
                if (BMLite_mFull == false)
                    _BMLite_StartChrg();
            }
#endif
            if (!_BMLite_mDCConnected) // 之前未接�?
            {
                _BMLite_mDCConnected = true;
                BMLite_Event(BMLITE_EV_DC_PULL_IN); // 通知充电器接入事�?
            }
#ifdef _BMLITE_USE_FLOAT_VOLTAGE_CPST
            if (adv < _BMLITE_FLOAT_VOLTAGE_ADV2)
            {
                BMLite_mFull = false;
            }else
#endif            
#if (_BMLITE_AD_MODE == 0)
            if (adv > _BMLITE_FLOAT_VOLTAGE_ADV)
#else
            if (adv < _BMLITE_FLOAT_VOLTAGE_ADV)
#endif
            {
#ifdef _BMLITE_USE_FLOAT_VOLTAGE_CPST
                // 满电标志维持上一次的状态不变
#else
                BMLite_mFull = false;
#endif                
            }
#if (_BMLITE_AD_MODE == 0)
            else if (adv > _BMLITE_OVER_VOLTAGE_ADV)
#else
            else if (adv < _BMLITE_OVER_VOLTAGE_ADV)
#endif
            {
                BMLite_mFloatTime++;
                if (BMLite_mFloatTime >= _BMLITE_FLOAT_TIME_VAL)
                {
                    BMLite_mFull = true;
                }
            }
            else
            {
                BMLite_mFull = true;
            }
            if (BMLite_mFull == false) // 不是满电，说明正在充�?
            {
                if (_BMLite_mIsCharging == false)
                {
                    _BMLite_mIsCharging = true;
                    BMLite_Event(BMLITE_EV_START_CHARGE); // 通知开始充�?
                }
            }
            else // 充满�?
            {
                if (_BMLite_mIsCharging)
                {
                    _BMLite_mIsCharging = false;
                    BMLite_Event(BMLITE_EV_CHARGE_FULL); // 通知已充满（停止充电�?
                }
            }
            if (_BMLite_mNoBattery)
            {
#if (_BMLITE_AD_MODE == 0)
                if (adv < _BMLITE_HAS_BATTERY_VOLTAGE_ADV)
#else
                if (adv > _BMLITE_HAS_BATTERY_VOLTAGE_ADV)
#endif
                {
                    _BMLite_mNoBattery = false;
                    //BMLite_Event(BMLITE_EV_HAS_BATTERY);   // 通知有电�?
                }
            }
        }
        else // 充电器移除了
        {
#ifdef _BMLITE_USE_DC_OUT_DELAY
            if (BMLite_mDcOutTime < 255)
                BMLite_mDcOutTime++;
            if (BMLite_mDcOutTime >= _BMLITE_DC_OUT_DELAY_TIME / 100)
#endif
            {
#ifdef _BMLITE_USE_FLOAT_VOLTAGE_CPST
                if (adv < _BMLITE_FLOAT_VOLTAGE_ADV2)
#else
#if (_BMLITE_AD_MODE == 0)
                if (adv > _BMLITE_FLOAT_VOLTAGE_ADV)
#else
                if (adv < _BMLITE_FLOAT_VOLTAGE_ADV)
#endif
#endif
                {
                    BMLite_mFull = false;
                    BMLite_mFloatTime = 0;
                }
                if (!_BMLite_mNoBattery)
                {
#if (_BMLITE_AD_MODE == 0)
                    if (adv > _BMLITE_NO_BATTERY_VOLTAGE_ADV)
#else
                    if (adv < _BMLITE_NO_BATTERY_VOLTAGE_ADV)
#endif
                    {
                        _BMLite_mNoBattery = true;
                        //BMLite_Event(BMLITE_EV_NO_BATTERY);   // 通知没电�?
                    }
                }
                if (_BMLite_mDCConnected)
                {
                    _BMLite_mDCConnected = false;
                    _BMLite_mIsCharging = false;
#ifdef _BMLITE_USE_SWST
                    BMLite_mDcInTime = 0;
#endif
                    BMLite_Event(BMLITE_EV_DC_PULL_OUT);
                }
            }
        }
        // TempProtect();      // 温度保护
    }
}

// 以下是内部函�?

//刷新充电状态【已被直接包含�?
// static void RefreshStat()
// {
//     bmlite_adv_t adv;
// #if (defined _BMLITE_ADC_ONLY_ON) && (defined _BMLITE_USE_SWST)
//     if (_BMLite_mDCConnected)
//     {
//         if (BMLite_mDcInTime >= 1)
//             adv = _BMLite_GetADValue();
//     }
//     else
//         adv = _BMLite_GetADValue();
// #else
//     adv = _BMLite_GetADValue();
// #endif
// #ifdef _BMLITE_USE_BATT_LEVEL
//         // 更新电池电量
// #if (_BMLITE_AD_MODE == 0)
//     if (adv <= _BMLITE_L100_ADV)
//         _BMLite_mLevel = 100;
//     else if (adv <= _BMLITE_L80_ADV)
//         _BMLite_mLevel = 80;
//     else if (adv <= _BMLITE_L60_ADV)
//         _BMLite_mLevel = 60;
//     else if (adv <= _BMLITE_L40_ADV)
//         _BMLite_mLevel = 40;
//     else if (adv <= _BMLITE_L20_ADV)
//         _BMLite_mLevel = 20;
//     else if (adv <= _BMLITE_L5_ADV)
//         _BMLite_mLevel = 5;
//     else
//         _BMLite_mLevel = 0;
// #else
//     if (adv >= _BMLITE_L100_ADV)
//         _BMLite_mLevel = 100;
//     else if (adv >= _BMLITE_L80_ADV)
//         _BMLite_mLevel = 80;
//     else if (adv >= _BMLITE_L60_ADV)
//         _BMLite_mLevel = 60;
//     else if (adv >= _BMLITE_L40_ADV)
//         _BMLite_mLevel = 40;
//     else if (adv >= _BMLITE_L20_ADV)
//         _BMLite_mLevel = 20;
//     else if (adv >= _BMLITE_L5_ADV)
//         _BMLite_mLevel = 5;
//     else
//         _BMLite_mLevel = 0;
// #endif
// #endif
//     if (_BMLite_GetDCStatus()) //充电器接�?
//     {
// #ifdef _BMLITE_USE_DC_OUT_DELAY
//         BMLite_mDcOutTime = 0;
// #endif
// #ifdef _BMLITE_USE_SWST
//         BMLite_mDcInTime++;
//         if (BMLite_mDcInTime == 10)
//         {
//             BMLite_mDcInTime = 0;
//             _BMLite_StopChrg();
//         }
//         else if (BMLite_mDcInTime == 1)
//         {
//             if (BMLite_mFull == false)
//                 _BMLite_StartChrg();
//         }
// #endif
//         if (!_BMLite_mDCConnected) // 之前未接�?
//         {
//             _BMLite_mDCConnected = true;
//             BMLite_Event(BMLITE_EV_DC_PULL_IN); // 通知充电器接入事�?
//         }
// #if (_BMLITE_AD_MODE == 0)
//         if (adv > _BMLITE_FLOAT_VOLTAGE_ADV)
// #else
//         if (adv < _BMLITE_FLOAT_VOLTAGE_ADV)
// #endif
//         {
//             BMLite_mFull = false;
//         }
// #if (_BMLITE_AD_MODE == 0)
//         else if (adv > _BMLITE_OVER_VOLTAGE_ADV)
// #else
//         else if (adv < _BMLITE_OVER_VOLTAGE_ADV)
// #endif
//         {
//             BMLite_mFloatTime++;
//             if (BMLite_mFloatTime == _BMLITE_FLOAT_TIME_VAL)
//             {
//                 BMLite_mFull = true;
//             }
//         }
//         else
//         {
//             BMLite_mFull = true;
//         }
//         if (BMLite_mFull == false) // 不是满电，说明正在充�?
//         {
//             if (_BMLite_mIsCharging == false)
//             {
//                 _BMLite_mIsCharging = true;
//                 BMLite_Event(BMLITE_EV_START_CHARGE); // 通知开始充�?
//             }
//         }
//         else // 充满�?
//         {
//             if (_BMLite_mIsCharging)
//             {
//                 _BMLite_mIsCharging = false;
//                 BMLite_Event(BMLITE_EV_CHARGE_FULL); // 通知已充满（停止充电�?
//             }
//         }
//         if (_BMLite_mNoBattery)
//         {
// #if (_BMLITE_AD_MODE == 0)
//             if (adv < _BMLITE_HAS_BATTERY_VOLTAGE_ADV)
// #else
//             if (adv > _BMLITE_HAS_BATTERY_VOLTAGE_ADV)
// #endif
//             {
//                 _BMLite_mNoBattery = false;
//                 //BMLite_Event(BMLITE_EV_HAS_BATTERY);   // 通知有电�?
//             }
//         }
//     }
//     else // 充电器移除了
//     {
// #ifdef _BMLITE_USE_DC_OUT_DELAY
//         if (BMLite_mDcOutTime < 255)
//             BMLite_mDcOutTime++;
//         if (BMLite_mDcOutTime >= _BMLITE_DC_OUT_DELAY_TIME / 100)
// #endif
//         {
// #if (_BMLITE_AD_MODE == 0)
//             if (adv > _BMLITE_FLOAT_VOLTAGE_ADV)
// #else
//             if (adv < _BMLITE_FLOAT_VOLTAGE_ADV)
// #endif
//             {
//                 BMLite_mFull = false;
//                 BMLite_mFloatTime = 0;
//             }
//             if (!_BMLite_mNoBattery)
//             {
// #if (_BMLITE_AD_MODE == 0)
//                 if (adv > _BMLITE_NO_BATTERY_VOLTAGE_ADV)
// #else
//                 if (adv < _BMLITE_NO_BATTERY_VOLTAGE_ADV)
// #endif
//                 {
//                     _BMLite_mNoBattery = true;
//                     //BMLite_Event(BMLITE_EV_NO_BATTERY);   // 通知没电�?
//                 }
//             }
//             if (_BMLite_mDCConnected)
//             {
//                 _BMLite_mDCConnected = false;
//                 _BMLite_mIsCharging = false;
// #ifdef _BMLITE_USE_SWST
//                 BMLite_mDcInTime = 0;
// #endif
//                 BMLite_Event(BMLITE_EV_DC_PULL_OUT);
//             }
//         }
//     }
// }
